import json

from django.core.paginator import Paginator
from django.http import JsonResponse
from django.shortcuts import render
from django.utils import timezone
# Create your views here.
from django.views import View
from django_redis import get_redis_connection

from goods.models import GoodsCategory, SKU, GoodsVisitCount
from goods.utils import get_categories
from orders.models import OrderGoods


class ListView(View):
    def get(self, request, category_id, page_num):
        # 获取商品列表页
        # 取sort参数, 来确定排序的关键字
        sort = request.GET.get('sort', 'default')
        if sort == 'price':  # 点击价格按钮
            sort_key = '-price'
        elif sort == 'hot':  # 点击人气
            sort_key = '-sales'
        else:  # 点击默认按钮
            sort_key = '-create_time'

        # 商品分类
        data = get_categories()

        # 面包屑, 三级分类
        breadcrumb = GoodsCategory.objects.get(id=category_id)

        # 获取当前页的商品信息
        skus = SKU.objects.filter(category_id=category_id).order_by(sort_key)

        # 分页
        p = Paginator(skus, 5)

        # 获取当前页
        current_page = p.page(page_num)

        # 当前页对象
        current_skus = current_page.object_list

        # 当前页页面 page_num

        # 总页数
        total_page = p.num_pages

        context = {
            "categories": data,
            "breadcrumb": breadcrumb,
            "skus_page": current_skus,
            "current_page": page_num,
            "total_page": total_page,
            "category": breadcrumb,
            "sort": sort
        }

        return render(request, 'list.html', context=context)


class HotView(View):
    def get(self, request, category_id):
        # 获取某个分类的热门商品
        # 1, 接收数据
        pass

        # 2, 校验数据
        pass

        # 3, 处理业务
        # 取销量最高的前两个商品
        skus = SKU.objects.filter(category_id=category_id, is_launched=True).order_by('-sales')[0:2]

        skus_list = []

        for sku in skus:
            sku_data = {
                'id': sku.id,
                'name': sku.name,
                'price': sku.price,
                'default_image_url': sku.default_image_url.url
            }
            skus_list.append(sku_data)

        # 4, 返回响应
        res = {
            'code': 0,
            'errmsg': '成功',
            'hot_skus': skus_list
        }

        return JsonResponse(res)


class DetailView(View):
    def get(self, request, sku_id):
        # 渲染商品详情页
        # 获取sku
        sku = SKU.objects.get(id=sku_id)

        # 商品分类
        data = get_categories()

        # 面包屑, 三级分类

        category_id = sku.category_id
        cat3 = GoodsCategory.objects.get(id=category_id)

        # sku的规格信息
        # 获取当前sku的信息
        try:
            sku = SKU.objects.get(id=sku_id)
        except SKU.DoesNotExist:
            return render(request, '404.html')

        # 构建当前商品的规格键
        sku_specs = sku.specs.order_by('spec_id')
        sku_key = []
        for spec in sku_specs:
            sku_key.append(spec.option.id)
        # 获取当前商品的所有SKU
        skus = sku.spu.sku_set.all()
        # 构建不同规格参数（选项）的sku字典
        spec_sku_map = {}
        for s in skus:
            # 获取sku的规格参数
            s_specs = s.specs.order_by('spec_id')
            # 用于形成规格参数-sku字典的键
            key = []
            for spec in s_specs:
                key.append(spec.option.id)
            # 向规格参数-sku字典添加记录
            spec_sku_map[tuple(key)] = s.id
        # 获取当前商品的规格信息
        goods_specs = sku.spu.specs.order_by('id')
        # 若当前sku的规格信息不完整，则不再继续
        if len(sku_key) < len(goods_specs):
            return
        for index, spec in enumerate(goods_specs):
            # 复制当前sku的规格键
            key = sku_key[:]
            # 该规格的选项
            spec_options = spec.options.all()
            for option in spec_options:
                # 在规格参数sku字典中查找符合当前规格的sku
                key[index] = option.id
                option.sku_id = spec_sku_map.get(tuple(key))
            spec.spec_options = spec_options

        context = {
            "categories": data,
            "breadcrumb": cat3,
            "sku": sku,
            'specs': goods_specs,
        }
        return render(request, 'detail.html', context=context)


class DetailVisitView(View):
    def post(self, request, category_id):
        # 统计分类访问量
        # 1, 接收数据
        # 2, 校验数据
        try:
            cat = GoodsCategory.objects.get(id=category_id)
        except Exception as e:
            print(e)
            return JsonResponse({'code': 9999, 'errmsg': '分类id不存在'})

        # 3, 处理业务
        # 获取当前日期
        today_date = timezone.localdate()
        try:
            gv = GoodsVisitCount.objects.get(category=cat,date=today_date)
            gv.count = gv.count +1
            gv.save()
        except Exception as e:
            GoodsVisitCount.objects.create(
                category=cat,
                count=1,
                date=today_date
            )

        # 4, 返回响应

        res = {
            'code': 0,
            'errmsg': '成功'
        }
        return JsonResponse(res)

        pass


class BrowseHistoryView(View):
    def post(self, request):
        # 保存浏览记录
        # 1, 接收数据
        # sku_id: "16"
        data = json.loads(request.body.decode())
        sku_id = data.get('sku_id')

        # 2, 校验数据
        # 获取user对象
        user = request.user
        if user.is_authenticated:
            pass
        else:
            return JsonResponse({'code':9999, 'errmsg':'未登录'})

        try:
            sku = SKU.objects.get(id=sku_id)
        except Exception as e:
            print(e)
            return JsonResponse({'code':9999, 'errmsg':'商品id有误'})

        # 3, 处理业务,  保存在redis history 这个缓存里
        # 获取redis 客户端
        redis_client = get_redis_connection('history')

        # 存入 history_userid 列表,
        # 逻辑 1,2,3
        # 1, 去重
        history = redis_client.lrange('history_%s'%user.id, 0, -1)
        if history:
            redis_client.lrem('history_%s'%user.id, 0, sku_id)
        # 2, 加入
        redis_client.lpush('history_%s' % user.id, sku_id)
        # 3, 截取
        redis_client.ltrim('history_%s' % user.id, 0, 4)

        # 4, 返回响应
        res = {
            'code':0,
            'errmsg':'成功'
        }
        return JsonResponse(res)
        pass


class GoodsCommentView(View):
    """订单商品评价信息"""

    def get(self, request, sku_id):
        # 获取被评价的订单商品信息
        order_goods_list = OrderGoods.objects.filter(sku_id=sku_id, is_commented=True).order_by('-create_time')[:30]
        # 序列化
        comment_list = []
        for order_goods in order_goods_list:
            username = order_goods.order.user.username
            comment_list.append({
                'username': username[0] + '***' + username[-1] if order_goods.is_anonymous else username,
                'comment':order_goods.comment,
                'score':order_goods.score,
            })
        return JsonResponse({'code':0, 'errmsg':'OK', 'goods_comment_list': comment_list})